package com.zmn.plat.business.impl.warranty.info;

import java.util.*;
import java.util.stream.Collectors;

import javax.annotation.Resource;

import com.zmn.common.constant.GlobalConsts;
import com.zmn.plat.common.dictionary.ProductDict;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang.StringUtils;
import org.springframework.stereotype.Service;

import com.aliyun.openservices.shade.io.netty.util.internal.StringUtil;
import com.google.common.collect.Lists;
import com.zmn.common.dto.VtDTO;
import com.zmn.common.utils.collection.CollectionUtil;
import com.zmn.common.utils.number.NumberUtil;
import com.zmn.plat.business.interfaces.warranty.info.WarrantyInfoBService;
import com.zmn.plat.common.constant.WarrantyConsts;
import com.zmn.plat.common.dictionary.PlatErrorCodeDict;
import com.zmn.plat.common.dictionary.WarrantyRuleEnum;
import com.zmn.plat.common.dto.warranty.WarrantyInfoDRO;
import com.zmn.plat.common.exception.PlatException;
import com.zmn.plat.model.entity.product.ServProduct;
import com.zmn.plat.model.entity.service.group.ServiceGroupQuery;
import com.zmn.plat.model.entity.warranty.content.WarrantyContent;
import com.zmn.plat.model.entity.warranty.content.WarrantyContentQuery;
import com.zmn.plat.model.entity.warranty.info.WarrantyInfo;
import com.zmn.plat.model.entity.warranty.info.WarrantyInfoExport;
import com.zmn.plat.model.entity.warranty.info.WarrantyInfoQuery;
import com.zmn.plat.services.interfaces.product.ServProductService;
import com.zmn.plat.services.interfaces.warranty.content.WarrantyContentService;
import com.zmn.plat.services.interfaces.warranty.info.WarrantyInfoService;

import lombok.extern.slf4j.Slf4j;

@Service
@Slf4j
public class WarrantyInfoBServiceImpl implements WarrantyInfoBService {

    @Resource
    WarrantyInfoService warrantyInfoService;
    @Resource
    WarrantyContentService warrantyContentService;
    @Resource
    ServProductService servProductService;

    @Override
    public WarrantyInfoDRO listWarrantyInfoByBizTypeAndProductIdAndItemIdAndTariffId(Integer bizType, Integer productId, List<Integer> itemIds, Integer traiffId) {
        if (NumberUtil.isNullOrZero(bizType) || NumberUtil.isNullOrZero(productId) || CollectionUtil.isNullOrEmpty(itemIds)) {
            log.error("入参为空或0,{},{},{}", bizType, productId, traiffId);
            throw new PlatException(PlatErrorCodeDict.ERROR_CODE_PANAM_NULL);
        }

        ServProduct product = servProductService.findByKey(productId);
        if (Objects.isNull(product) || Objects.isNull(product.getServCategId()) || Objects.isNull(product.getCategOneId()) || Objects.isNull(product.getCategId())) {
            log.error("产品不存在或产品数据异常 {}，errorCode:{}", product, PlatErrorCodeDict.ERROR_CODE_WARRANTY_PRODUCT_NULL_OR_INVALIDAE);
            throw new PlatException(PlatErrorCodeDict.ERROR_CODE_WARRANTY_PRODUCT_NULL_OR_INVALIDAE);
        }

        WarrantyInfoQuery query = new WarrantyInfoQuery();
        query.setBizType(bizType);
        query.setServCategId(product.getServCategId());
        query.setCategOneId(product.getCategOneId());
        query.setCategId(product.getCategId());
        query.setItemIds(itemIds);
        if (NumberUtil.isPositiveInteger(traiffId)) {
            query.setTariffId(traiffId);
        }
        List<WarrantyInfo> warrantyInfos = warrantyInfoService.listByQuery(query);

        if (org.springframework.util.CollectionUtils.isEmpty(warrantyInfos)) {
            log.error("warrantyInfos is null,errorCode:{}", PlatErrorCodeDict.ERROR_CODE_WARRANTY_NOT_EXISTS);
            throw new PlatException(PlatErrorCodeDict.ERROR_CODE_WARRANTY_NOT_EXISTS);
        }

        // 如果只有一条数据，直接返回对应保修信息
        if (warrantyInfos.size() == 1) {
            WarrantyInfo warrantyInfo = warrantyInfos.get(0);
            return returnWarrantyInfoDRO(warrantyInfo);
        }

        // 取优先级
        List<WarrantyInfo> warrantyInfoList = this.getVailteWarrantyInfoList(warrantyInfos, WarrantyConsts.RULE_MACHINEWARRANTY);
        if (org.springframework.util.CollectionUtils.isEmpty(warrantyInfoList)) {
            log.error("warrantyInfoList is null,errorCode:{}", PlatErrorCodeDict.ERROR_CODE_WARRANTY_INFO_NONE);
            throw new PlatException(PlatErrorCodeDict.ERROR_CODE_WARRANTY_INFO_NONE);
        }

        if (warrantyInfoList.size() == 1) {
            return returnWarrantyInfoDRO(warrantyInfoList.get(0));
        }

        WarrantyInfo warrantyInfoTotal = warrantyInfoList.get(0);
        for (int i = 1; i < warrantyInfoList.size(); i++) {
            WarrantyInfo info = warrantyInfoList.get(i);
            warrantyInfoTotal.setWarrantyContentIdStr(warrantyInfoTotal.getWarrantyContentIdStr() + "$" + info.getWarrantyContentIdStr());
            warrantyInfoTotal.setWarrantyDurationStr(warrantyInfoTotal.getWarrantyDurationStr() + "$" + info.getWarrantyDurationStr());

            // 优先级：已延长>不延长。已延迟取最长的时间为准
            Integer currentMaxExtendedDuration = Objects.isNull(warrantyInfoTotal.getExtendedDuration()) ? 0 : warrantyInfoTotal.getExtendedDuration();
            if (Objects.equals(GlobalConsts.YES, info.getExtendType())) {
                warrantyInfoTotal.setExtendType(GlobalConsts.YES);
                if (currentMaxExtendedDuration < info.getExtendType()) {
                    warrantyInfoTotal.setExtendedDuration(info.getExtendedDuration());
                }
            }
        }

        return returnWarrantyInfoDRO(warrantyInfoTotal);
    }

    @Override
    public ArrayList<List> outputProductExcel(ServiceGroupQuery query) {

        WarrantyContentQuery contentQuery = new WarrantyContentQuery();
        List<WarrantyContent> warrantyContents = warrantyContentService.listByQuery(contentQuery);
        Map<Integer, String> contentMap = warrantyContents.stream().collect(Collectors.toMap(WarrantyContent::getWarrantyContentId, WarrantyContent::getContent));

        List<WarrantyInfoExport> warrantyInfoExports = warrantyInfoService.listExportExcelPageByQuery(query);

        ArrayList<List> arrayList = Lists.newArrayListWithExpectedSize(warrantyInfoExports.size() + 1);
        List<String> column = Arrays.asList(WarrantyConsts.WARRANTY_TITLE);
        arrayList.add(column);

        if (CollectionUtils.isNotEmpty(warrantyInfoExports)) {
            warrantyInfoExports.forEach(warrantyInfoExport -> {
                List<String> item = new ArrayList<>();
                item.add(warrantyInfoExport.getServCategName());
                item.add(warrantyInfoExport.getCategOneName());
                item.add(Objects.nonNull(warrantyInfoExport.getGroupId())?warrantyInfoExport.getGroupId().toString():"");
                item.add(warrantyInfoExport.getGroupName());
                item.add(Objects.nonNull(warrantyInfoExport.getItemId())?warrantyInfoExport.getItemId().toString():"");
                item.add(warrantyInfoExport.getItemName());
                item.add(warrantyInfoExport.getStatus());
                item.add(warrantyInfoExport.getCategName());
                // 啄木鸟保修信息
                item.add(NumberUtil.isNullOrZero(warrantyInfoExport.getRule()) ? "" : WarrantyRuleEnum.of(warrantyInfoExport.getRule()).getName());
                item.add(StringUtils.isEmpty(warrantyInfoExport.getDurationStr()) ? "" : trimBothEndsChars(warrantyInfoExport.getDurationStr(), "\\$").replaceAll("\\$", ";"));
                if (StringUtils.isNotEmpty(warrantyInfoExport.getContentIdStr())) {
                    String zmnContentIdStr = warrantyInfoExport.getContentIdStr();
                    zmnContentIdStr = trimBothEndsChars(zmnContentIdStr, "\\$");
                    String[] zmnContentIdArr = zmnContentIdStr.split("\\$");
                    StringBuilder sb = new StringBuilder();
                    for (int i = 0; i < zmnContentIdArr.length; i++) {
                        sb.append(i == 0 ? contentMap.get(Integer.parseInt(zmnContentIdArr[i])) : ";" + contentMap.get(Integer.parseInt(zmnContentIdArr[i])));
                    }
                    item.add(sb.toString());
                } else {
                    item.add("");
                }

                item.add(Objects.equals(GlobalConsts.YES, warrantyInfoExport.getExtendType()) ? "延长" : "不延长");
                item.add(Objects.isNull(warrantyInfoExport.getExtendedDuration()) ? "" : "" + warrantyInfoExport.getExtendedDuration());
                item.add(ProductDict.getBizTypeCNENName(warrantyInfoExport.getBizType()));

                arrayList.add(item);
            });
        }
        return arrayList;
    }

    private List<WarrantyInfo> getVailteWarrantyInfoList(List<WarrantyInfo> warrantyInfos, Integer rule) {
        List<WarrantyInfo> warrantyInfoList = new ArrayList<>();
        WarrantyInfo warrantyInfo;
        for (int i = 0; i < warrantyInfos.size(); i++) {
            warrantyInfo = warrantyInfos.get(i);
            if (Objects.equals(rule, warrantyInfo.getRuleId())) {
                warrantyInfoList.add(warrantyInfo);
            }
        }

        if (Objects.equals(0, rule)) {
            return warrantyInfoList;
        }

        // 不保修优先级最后
        if (Objects.equals(WarrantyConsts.RULE_SAMENATUREFAULT, rule)) {
            rule = 0;
        }

        return org.springframework.util.CollectionUtils.isEmpty(warrantyInfoList) ? getVailteWarrantyInfoList(warrantyInfos, rule + 1) : warrantyInfoList;

    }

    private WarrantyInfoDRO returnWarrantyInfoDRO(WarrantyInfo warrantyInfo) {

        Integer ruleId = warrantyInfo.getRuleId();
        WarrantyInfoDRO warrantyInfoDRO = new WarrantyInfoDRO();
        warrantyInfoDRO.setRuleId(ruleId);
        if (Objects.equals(ruleId, WarrantyConsts.RULE_NOWARRANTY)) {
            return warrantyInfoDRO;
        }

        String warrantyContentIdStr = warrantyInfo.getWarrantyContentIdStr();
        String warrantyDurationStr = warrantyInfo.getWarrantyDurationStr();
        if (StringUtil.isNullOrEmpty(warrantyContentIdStr) || StringUtil.isNullOrEmpty(warrantyDurationStr)) {
            log.error("returnWarrantyInfoDRO,保修信息配置有误,errorCode:{}", PlatErrorCodeDict.ERROR_CODE_WARRANTY_CONFIG_ERROR);
            throw new PlatException(PlatErrorCodeDict.ERROR_CODE_WARRANTY_CONFIG_ERROR);
        }

        String[] contentIdStrArr = warrantyContentIdStr.split("\\$");
        List<Integer> contentIdList = new ArrayList<>(contentIdStrArr.length);
        for (String tmpId : contentIdStrArr) {
            if (com.zmn.common.utils.string.StringUtil.isBlank(tmpId.trim())) {
                continue;
            }
            contentIdList.add(Integer.parseInt(tmpId.trim()));
        }

        contentIdList = contentIdList.stream().distinct().collect(Collectors.toList());
        List<WarrantyContent> warrantyContents = warrantyContentService.findByKeys(contentIdList);
        List<VtDTO> collect = warrantyContents.stream().map(m -> new VtDTO(m.getWarrantyContentId(), m.getContent())).collect(Collectors.toList());
        warrantyInfoDRO.setContentVtList(collect);

        String[] durationStrArr = warrantyDurationStr.split("\\$");
        if (durationStrArr != null && durationStrArr.length > 0) {
            List<String> durationStrList = Arrays.asList(durationStrArr).stream().filter(e -> com.zmn.common.utils.string.StringUtil.isNotBlank(e)).distinct().collect(Collectors.toList());
            warrantyInfoDRO.setDays(new HashSet<>(durationStrList));
        }

        warrantyInfoDRO.setExtendType(warrantyInfo.getExtendType());
        warrantyInfoDRO.setExtendedDuration(warrantyInfo.getExtendedDuration());

        return warrantyInfoDRO;
    }

    private String trimBothEndsChars(String srcStr, String splitter) {
        String regex = "^" + splitter + "*|" + splitter + "*$";
        return srcStr.replaceAll(regex, "");
    }
}
